
use rocket::Route;
use rocket::serde::{Deserialize, Serialize, json::Json, json::Value, json::json};
use rocket::form::{Form, FromForm};

pub fn all() -> Vec<Route> {
    routes![restful_path, query_params, query_struct, submit_form, post_json, post_json2]
}

#[derive(Deserialize, Serialize)]
pub struct User {
    name: String,
    age: u16
}

#[derive(FromForm)]
pub struct UserForm {
    name: String,
    age: u16
}

#[derive(Serialize)]
pub struct SimpleResponse {
    msg: String,
    status: i16,
    data: User
}

#[get("/restful/<name>/<age>")]
pub fn restful_path(name: String, age: u8) -> String {
    format!("Hello, {} year old named {}! (resource-paths)", age, name)
}

#[get("/query1?<name>&<age>")]
pub fn query_params(name: String, age: Option<u8>) -> String {
    match age {
        Some(_age) => format!("Hello, {} year old named {}! (query-params)", _age, name),
        None => format!("Hello, {}! without param age. (query-params)", name)
    }
}

#[get("/query2?<user..>")]
pub fn query_struct(user: UserForm) -> String {
    format!("Hello, {} year old named {}! (query-struct)", user.age, user.name)
}

#[post("/submit", data = "<user>")]
pub fn submit_form(user: Form<UserForm>) -> String {
    format!("Hello, {} year old named {}! (post-form)", user.age, user.name)
}

#[post("/post1", data = "<user>")]
pub fn post_json(user: Json<User>) -> Value {
    json!({ "msg": "success", "status": 0, "data": {"name": user.name, "age": user.age} })
}

#[post("/post2", data = "<user>")]
pub fn post_json2(user: Json<User>) -> Json<SimpleResponse> {
    Json(SimpleResponse { msg: String::from("success"), status: 0, data: user.0 })
}